Appearance
[中文版本](/posts/c教程/zh-CN/03-内存/023-Arrays and Pointer Arithmetic)
An array is a block of consecutive memory cells that hold elements of the same type. Arrays and pointers are deeply connected in C, in fact, an array’s name often behaves like a pointer to its first element. Understanding how arrays and pointer arithmetic work together is key to writing fast, memory-efficient programs.
Declaring and Using Arrays
#include <stdio.h>
int main(void) {
int numbers[5] = {10, 20, 30, 40, 50};
for (int i = 0; i < 5; i++) {
printf("numbers[%d] = %d\n", i, numbers[i]);
}
return 0;
}Output:
numbers[0] = 10
numbers[1] = 20
numbers[2] = 30
numbers[3] = 40
numbers[4] = 50Here:
numbersis an array of five integers.- Each element is stored next to each other in memory.
- The compiler knows each
inttakes the same number of bytes, so it can findnumbers[i]quickly using pointer arithmetic.
Array Name as a Pointer
When you use an array’s name (without an index), it acts as a pointer to its first element.
int numbers[3] = {1, 2, 3};
int *p = numbers; // same as &numbers[0]
printf("%d %d %d\n", *p, *(p + 1), *(p + 2));Output:
1 2 3Each time you add 1 to the pointer, it moves forward by one element, not one byte, but one object of that type.
Tiny Code
Here’s a complete example showing array access and pointer arithmetic:
#include <stdio.h>
int main(void) {
int arr[5] = {2, 4, 6, 8, 10};
int *ptr = arr; // arr decays to pointer to arr[0]
printf("Accessing with array index:\n");
for (int i = 0; i < 5; i++) {
printf("arr[%d] = %d\n", i, arr[i]);
}
printf("\nAccessing with pointer arithmetic:\n");
for (int i = 0; i < 5; i++) {
printf("*(ptr + %d) = %d\n", i, *(ptr + i));
}
printf("\nAddresses in memory:\n");
for (int i = 0; i < 5; i++) {
printf("&arr[%d] = %p\n", i, (void *)&arr[i]);
}
return 0;
}Compile and run:
gcc array_pointer.c -o array_pointer
./array_pointerOutput (addresses will differ):
Accessing with array index:
arr[0] = 2
arr[1] = 4
arr[2] = 6
arr[3] = 8
arr[4] = 10
Accessing with pointer arithmetic:
*(ptr + 0) = 2
*(ptr + 1) = 4
*(ptr + 2) = 6
*(ptr + 3) = 8
*(ptr + 4) = 10
Addresses in memory:
&arr[0] = 0x7ffcc73f9a60
&arr[1] = 0x7ffcc73f9a64
&arr[2] = 0x7ffcc73f9a68
&arr[3] = 0x7ffcc73f9a6c
&arr[4] = 0x7ffcc73f9a70You can see that each element sits 4 bytes apart (typical size ofint).
Pointer Arithmetic Rules
When you move pointers, C automatically scales by the size of the type they point to:
| Expression | Meaning |
|---|---|
p + 1 | Move to the next element |
p - 1 | Move to the previous element |
*(p + i) | Access the i-th element after the current one |
p2 - p1 | Returns the number of elements between two pointers |
Example:
int *start = arr;
int *end = arr + 5;
printf("Array length: %ld\n", end - start); // prints 5Common Pitfalls
Out-of-bounds access Accessing memory beyond an array’s valid range leads to undefined behavior:
arr[5] = 99; // invalid! array has only indices 0-4Array decay Arrays “decay” to pointers when passed to functions, they lose size information. You must pass the length manually.
void print_array(int *arr, int len);Pointer confusion Remember thatarr[i] and*(arr + i) mean the same thing. Mixing them is fine, but be consistent for readability.
Why It Matters
Arrays and pointers form the foundation of C data structures. You’ll use them to build:
- Strings (arrays of
char) - Matrices (arrays of arrays)
- Linked lists and trees (via pointer arithmetic)
Once you’re comfortable thinking of arrays as contiguous memory blocks accessed through pointers, you can start designing your own data structures like a real systems programmer.
Try It Yourself
- Write a function that prints an array using only pointers (no
[]syntax). - Create an array of
charand print it as a string and as separate characters. - Declare an array of 10 numbers, then use pointers to sum them.
- Print the address difference between two elements.
- Create a two-dimensional array and print it with nested loops.
Arrays and pointers are two sides of the same coin in C. Once you understand their connection, you’ll see how powerful, and elegant, direct memory access can be.
